/*
 * Copyright 2021-2022 Open Kunlun Technology <https://www.openkunlun.io>
 */

package io.openkunlun.scalarpc.codegen.model

import scala.meta._

/**
 * @author kostas.kougios
 *         Date: 10/11/17
 */
case class DeclaredValEx private (meta: DeclaredValEx.Meta)
  extends ValEx
  with CodeEx.Name[DeclaredValEx]
  with TypeEx.Contains[DeclaredValEx] {
  override def tree: Decl.Val = Decl.Val(meta.mods.toList, meta.patsnel.toList, meta.tpe)
  override def name: String = meta.patsnel.collectFirst {
    case n: Pat.Var => n.name.value
  }.get

  override def withName(name: String): DeclaredValEx = copy(meta = meta.copy(patsnel = List(Pat.Var(Term.Name(name)))))

  override def `type`: TypeEx = TypeEx.apply(meta.tpe)
  override def withType(t: TypeEx): DeclaredValEx = copy(meta = meta.copy(tpe = t.meta.tpe))

  override def withMods(mods: ModsEx): DeclaredValEx = copy(meta = meta.copy(mods = mods.meta.mods.toList))
}

object DeclaredValEx extends PartialParser[DeclaredValEx] {
  case class Meta(mods: Seq[Mod], patsnel: Seq[scala.meta.Pat], tpe: Type) extends MetaEx with MetaEx.Mods

  override def parser: PartialFunction[Tree, DeclaredValEx] = {
    case q"..$mods val ..$patsnel: $tpe" =>
      DeclaredValEx(Meta(mods, patsnel, tpe))
  }

  trait Contains {
    def vals: Seq[DeclaredValEx]
  }
}
